﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Skywave.ComponentModel
{
    public class RemoteProfileManager
    {
        static System.Runtime.Serialization.DataContractSerializer serializer_ProfileList = new System.Runtime.Serialization.DataContractSerializer(typeof(RemoteProfileManagerProfilesCache));
        //
        public event EventHandler<RemoteProfileManagerProfileListEventArgs> ProfileList;
        public event EventHandler<RemoteProfileManagerProfileLoadEventArgs> ProfileLoad;
        //
        string path_Profiles_Downloaded = "Profiles_Downloaded.data";
        string path_Profiles_Storage = "Storage\\";
        string path_Base = "";
        System.IO.DirectoryInfo dir_Profiles_Storage;
        System.IO.FileInfo file_Profiles_Downloaded;
        //
        RemoteProfileManagerProfilesCache profiles_Cache;
        List<RemoteProfileManagerProfile> profiles_Retreived;

        public RemoteProfileManager(string storagePath)
        {
            path_Base = storagePath;
        }

        public void InitializeMe()
        {
            if (!path_Base.EndsWith("\\"))
                path_Base += "\\";
            if (!System.IO.Directory.Exists(path_Base))
                System.IO.Directory.CreateDirectory(path_Base);
            //
            dir_Profiles_Storage = new System.IO.DirectoryInfo(path_Base + path_Profiles_Storage);
            file_Profiles_Downloaded = new System.IO.FileInfo(path_Base + path_Profiles_Downloaded);
            //
            if (file_Profiles_Downloaded.Exists)
            {
                using (System.IO.FileStream fs1 = new System.IO.FileStream(file_Profiles_Downloaded.FullName, System.IO.FileMode.Open, System.IO.FileAccess.Read))
                {
                    profiles_Cache = serializer_ProfileList.ReadObject(fs1) as RemoteProfileManagerProfilesCache;
                }
            }
            if (profiles_Cache == null)
                profiles_Cache = new RemoteProfileManagerProfilesCache();
            //
            Profile_RetreiveList();
        }

        public void Profile_RetreiveList()
        {
            if (ProfileList != null)
            {
                RemoteProfileManagerProfileListEventArgs args1 = new RemoteProfileManagerProfileListEventArgs();
                ProfileList(this, args1);
                if (args1.Profiles != null)
                    profiles_Retreived = args1.Profiles;
                else
                    profiles_Retreived = new List<RemoteProfileManagerProfile>();
            }
            else
                profiles_Retreived = new List<RemoteProfileManagerProfile>();
        }

        public async Task<System.IO.DirectoryInfo> Load(int profileId)
        {
            System.IO.DirectoryInfo r = null;
            //
            if (ProfileLoad != null)
            {
                RemoteProfileManagerProfile profile_Selected = profiles_Retreived.SingleOrDefault(q => q.Id == profileId);
                if (profile_Selected != null)
                {
                    if (profiles_Cache != null && profiles_Cache.Profiles != null)
                    {
                        RemoteProfileManagerProfile profile_Selected_Downloaded = profiles_Cache.Profiles.SingleOrDefault(q => q.Id == profileId);
                        if (profile_Selected_Downloaded != null)
                        {
                            if (profile_Selected_Downloaded.LastUpdateDate == profile_Selected.LastUpdateDate)
                            {
                                r = new System.IO.DirectoryInfo(dir_Profiles_Storage.FullName + "\\" + profile_Selected_Downloaded.Id.ToString());
                                if (!r.Exists)
                                    r = null;
                            }
                        }
                    }
                    //
                    if (r == null)
                    {
                        RemoteProfileManagerProfileLoadEventArgs args1 = new RemoteProfileManagerProfileLoadEventArgs();
                        args1.Profile = profile_Selected;
                        ProfileLoad(this, args1);
                        IO.Compression.ZipStorer zip1 = null;
                        if (args1.ProfileContentZiped != null)
                            zip1 = IO.Compression.ZipStorerFile.Open(args1.ProfileContentZiped, System.IO.FileAccess.Read);
                        else if (!string.IsNullOrEmpty(args1.ProfilePathZiped) && System.IO.File.Exists(args1.ProfilePathZiped))
                            zip1 = await IO.Compression.ZipStorerFile.Open(args1.ProfilePathZiped, System.IO.FileAccess.Read);
                        //
                        if (zip1 != null)
                        {
                            r = new System.IO.DirectoryInfo(string.Format("{0}\\{1}\\", dir_Profiles_Storage.FullName, profile_Selected.Id));
                            if (!r.Exists)
                            {
                                r.Create();
                                r.Refresh();
                            }
                            //
                            string path;
                            List<IO.Compression.ZipStorer.ZipFileEntry> dir = zip1.ReadCentralDir();
                            foreach (IO.Compression.ZipStorer.ZipFileEntry entry in dir)
                            {
                                path = System.IO.Path.Combine(r.FullName, entry.FilenameInZip);
                                await zip1.ExtractFile(entry, path);
                            }
                            //
                            zip1.Close();
                        }
                    }
                    //
                    if (r != null)
                    {
                        profiles_Cache.Profiles.RemoveAll(q => q.Id == profile_Selected.Id);
                        profiles_Cache.Profiles.Add(profile_Selected);
                        profiles_Cache.DefaultProfileId = profile_Selected.Id;
                        using (System.IO.FileStream fs1 = new System.IO.FileStream(file_Profiles_Downloaded.FullName, System.IO.FileMode.Create, System.IO.FileAccess.Write))
                        {
                            serializer_ProfileList.WriteObject(fs1, profiles_Cache);
                        }
                    }
                }
            }
            //
            return r;
        }


        /// <summary>
        /// ...
        /// </summary>
        public List<RemoteProfileManagerProfile> Profiles
        {
            get { return profiles_Retreived; }
        }

        /// <summary>
        /// ...
        /// </summary>
        public int? DefaultProfileId
        {
            get { return (profiles_Cache == null) ? null : profiles_Cache.DefaultProfileId; }
        }

    }
}
